package com.charon.common.security.realm;

import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationInfo;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.subject.SimplePrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;

import com.charon.module.sys.dao.UserEntityMapper;
import com.charon.module.sys.entity.UserEntity;

/**
 * @ClassName：CustomRealm.java
 * @Description: 自定义Realm
 * @Author charon [248135724@qq.com]
 * @Date: 2018年11月30日 上午2:14:53
 * @version V1.0
 */
public class CustomRealm extends AuthorizingRealm {

	@Autowired
	private UserEntityMapper uem;

	@Override
	protected void clearCachedAuthorizationInfo(PrincipalCollection principals) {
		if(SecurityUtils.getSubject().isAuthenticated()){
			Object principal = principals.getPrimaryPrincipal();
			System.out.println("清理：======"+principal);
			SimplePrincipalCollection spc=new SimplePrincipalCollection(principal,this.getName());
			super.clearCachedAuthorizationInfo(spc);
		}
	}

	@Override
	protected void doClearCache(PrincipalCollection principals) {
		if(SecurityUtils.getSubject().isAuthenticated()){
			super.doClearCache(principals);
		}
	}

	/**
	 * 做授权
	 */
	@Override
	protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
		String userName = (String) principals.getPrimaryPrincipal();
		Set<String> roles = getRolesByUserName(userName);
		Set<String> permissions = getPermissionsByUserName(userName);
		System.out.println("开始授权：\n");
		System.out.println("roles:"+roles);
		System.out.println("permissions:"+permissions);
		//创建授权对象，并将数据库中的用户角色、权限信息设置到该对象中
		SimpleAuthorizationInfo sai = new SimpleAuthorizationInfo();
		sai.setStringPermissions(permissions);
		sai.setRoles(roles);
		return sai;
	}

	@Override
	protected void clearCache(PrincipalCollection principals) {
		super.clearCache(principals);
	}

	/**
	 * 做认证
	 */
	@Override
	protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
		// 从主体认证信息中获得用户名
		String userName = (String) token.getPrincipal();
		String password = getPasswordByUserName(userName);
		System.out.println("开始登陆：\n");
		System.out.println("userName："+userName);
		System.out.println("password："+password);
		if (password == null) {
			return null;
		}
		//创建认证对象，并将数据库中的用户信息设置到该对象中
		SimpleAuthenticationInfo sai = new SimpleAuthenticationInfo(userName, password, "admi");
		return sai;
	}
	
	/**
	 * @Description:根据用户名获取密码   
	 * @author:charon [248135724@qq.com]
	 * @date:   2018年12月18日 下午10:57:26 
	 * @param: @param userName
	 * @return: String
	 */
	private String getPasswordByUserName(String userName) {
		UserEntity ue = new UserEntity();
		ue.setAccount(userName);
		List<UserEntity> user = uem.findList(ue);
		System.out.println(user.get(0).toString());
		if (user != null && user.size() > 0)
			return user.get(0).getPassword();
		return null;
	}
	
	/**
	 * @Description: 根据用户名获取角色   
	 * @author:charon [248135724@qq.com]
	 * @date:   2018年12月18日 下午10:55:33 
	 * @param: @param userName
	 * @return: Set<String>
	 */
	private Set<String> getRolesByUserName(String userName) {
		System.out.println("从数据库中读取角色信息："+userName);
		UserEntity ue = new UserEntity();
		ue.setAccount(userName);
		List<UserEntity> user = uem.findList(ue);
		Set<String> set = new HashSet<String>();
		if (user != null && user.size() > 0 && user.get(0).getRole() != null && user.get(0).getRole().size() > 0) {
			for (int i = 0; i < user.get(0).getRole().size(); i++) {
				set.add(user.get(0).getRole().get(i).getRole());
			}
		}
		if (set != null && set.size() > 0)
			return set;
		return null;
	}
	/**
	 * @Description:根据用户名获取权限信息
	 * @author:charon [248135724@qq.com]
	 * @date:   2018年12月18日 下午10:55:50 
	 * @param: @param userName
	 * @param: @return      
	 * @return: Set<String>
	 */
	private Set<String> getPermissionsByUserName(String userName) {
		System.out.println("从数据库中读取权限信息："+userName);
		UserEntity ue = new UserEntity();
		ue.setAccount(userName);
		List<UserEntity> user = uem.findList(ue);
		if (user != null && user.size() > 0 && user.get(0).getRole() != null && user.get(0).getRole().size() > 0) {
			Set<String> set = new HashSet<String>();
			for (int i = 0; i < user.get(0).getRole().size(); i++) {
				for (int x = 0; x < user.get(0).getRole().get(i).getPermission().size(); x++) {
					set.add(user.get(0).getRole().get(i).getPermission().get(x).getPermission_value());
				}
			}
			if (set != null && set.size() > 0)
				return set;
		}
		return null;
	}

}
